import { ActionTree, Commit } from 'vuex'
import { RootState } from '@/store'
import { asyncRoutes } from '@/router'
import { AppRouteRecordRaw } from '@/router/types'
import { Roles } from '@/models/user-info'
import { PermissionMutationTypes } from './mutations'

export enum permissionActionTypes {
  ACTION_SET_ROUTES = 'ACTION_SET_ROUTES'
}

export interface PermissionActions {
  // 用户登录
  [permissionActionTypes.ACTION_SET_ROUTES](
    context: { commit: Commit },
    roles: Roles
  ): Promise<AppRouteRecordRaw[]>
}

/**
 *
 * @param roles
 * @param route
 * @returns
 */
const hasPermission = (roles: Roles, route: AppRouteRecordRaw) => {
  if (!route.meta || !route.meta.roles) return true
  return roles.some(role => route.meta?.roles?.includes(role))
}

const filterAsyncRoutes = (
  asyncRoutes: AppRouteRecordRaw[],
  roles: Roles
): AppRouteRecordRaw[] => {
  const res: AppRouteRecordRaw[] = []
  asyncRoutes.forEach(route => {
    const r = { ...route }
    if (hasPermission(roles, r)) {
      if (r.children && r.children.length > 0) {
        r.children = filterAsyncRoutes(r.children, roles)
      }
      res.push(r)
    }
  })

  return res
}

const actions: ActionTree<PermissionState, RootState> & PermissionActions = {
  [permissionActionTypes.ACTION_SET_ROUTES]({ commit }, roles: Roles) {
    return new Promise(resolve => {
      let accessedRoutes: AppRouteRecordRaw[] = []
      accessedRoutes = filterAsyncRoutes(asyncRoutes, roles)
      commit(PermissionMutationTypes.SET_ROUTES, accessedRoutes)
      resolve(accessedRoutes)
      return accessedRoutes
    })
  }
}

export default actions
